/*
 * TestPlanetaIntegracion.cpp
 *
 *  Created on: 20/02/2010
 *      Author: San Martín, Matías I.
 */

#include <unistd.h>
#include <sstream>

#include "MockMiddlewareIO.h"

#include "../../../Aplicacion/Modelo/EnPlaneta/Planeta.h"
#include "../../../Aplicacion/Common/Registry.h"
#include "../../../Aplicacion/Common/Mensajes/DatosMensajeFactory.h"
#include "MockDirectorio.h"

#include "../../../Middleware/EnPlaneta/MsjEmisor.h"
#include "../../../Middleware/EnPlaneta/MsjReceptorApp.h"
#include "../../../Middleware/EnPlaneta/MsjReceptorMid.h"

#include "../../../Framework/Shared/sem.h"
#include "../../../Framework/Shared/shptr.h"

using namespace std;
using namespace aplicacion::planeta;

static Semaphore semAccesoInfoPipe;
static Semaphore semLeyendoDatos;
static t_sharedRegistro datosRegitro;
static InformacionPlaneta infoPlanetaAlt;

static void inicializarRecursos()
{
	//creo recursos compartidos
	if (!semAccesoInfoPipe.init(1))
	{
		cout << "Fallo inicializacion semAccesoInfoPipe. " << endl;
		exit(-1);
	}


	if (!semLeyendoDatos.init(1))
	{
		cout << "Fallo inicializacion semLeyendoDatos. " << endl;
		exit(-1);
	}


	if (!datosRegitro.allocate())
	{
		cout << "Fallo creacion de datosRegistro. " << endl;
		exit(-1);
	}
}

static void liberarRecursos()
{
	cout << "Libero recursos" << endl;
	//no se usan mas los recursos compartidos
	semAccesoInfoPipe.destroy();
	semLeyendoDatos.destroy();
	datosRegitro.free();
}

int main(int argc, char **argv) {

	inicializarRecursos();

	IdUniverso idU(2);
	IdPlaneta idP(1,idU);

	//creo el "falso" middlewareIO
	MockMiddlewareIO midIO(idP);

	//lanzo los 2 procesos (middleware y aplicacion)
	pid_t pidMsjReceptorMid = fork();
	if (pidMsjReceptorMid == 0)
	{
		try
		{
			//ccreo e inicializo el proceso receptor que corre en el middleware
			MsjReceptorMidSingleton::instance().inicializar(&midIO,&semLeyendoDatos,&datosRegitro);
			MsjReceptorMidSingleton::instance().start();

		}catch (...)
		{
			cout << "Excepcion" << endl;
		}
	}else{
		/* en este proceso se ejecuta el MsjReceptorApp ya que necesita
		 * saber el pid del MsjReceptorMid	 */
		//creo el proceso receptor que corre "en la aplicacion"
		MsjReceptorApp recept;
		recept.inicializar(&semAccesoInfoPipe,&semLeyendoDatos,&datosRegitro,pidMsjReceptorMid);

		MsjEmisor emisor;
		emisor.inicializar(&midIO);

		//---------------------------- creacion del planeta ------------------

		IdJuego juego(4);
		IdJugador jugador(99,juego);
		IdUniverso idUni(21);
		infoPlanetaAlt._identificador.setId(20);
		infoPlanetaAlt._identificador.setContainerId(idUni);
		infoPlanetaAlt._duenio = jugador;
		infoPlanetaAlt._cantidadNaves = 10000;
		infoPlanetaAlt._tamanio = 11;
		infoPlanetaAlt._posicion.setXY(100,200);

		MockDirectorio dir;
		dir.addInformacionPlaneta(infoPlanetaAlt);
		RegistrySingleton::instance().setDirectorio(&dir);
		DatosMensajeFactorySingleton::instance().setContexto(DatosMensajeFactory::CONTEXTO_PLANETA);

		Posicion pos(20,25);

		//creo el planeta
		Planeta p(idP,15,pos);
		p.init(&recept,&emisor);

		//inicio ejecucion del planeta
		p.run();

		//--------------------------- fin ejecucion planeta -------------------
		liberarRecursos();

	}
}
